<template>
  <MenuPage
    :data="resData.list"
    :columns="columns"
    :page.sync="queryParams.pageIndex"
    :size.sync="queryParams.pageSize"
    :total="resData.total"
    :loading="resData.loading"
    @queryFun="getCommonVulnerabilityList">
    <template slot="search">
      <Button
        type="primary"
        ghost
        icon="md-cloud-download"
        style="height: 32px;margin-left: 9px;"
        @click="exportLeak()">导出当前页漏洞
      </Button>
      <Button ghost style="height: 32px;" type="primary" class="md-add-jh" @click="showAddModal()">创建漏洞信息</Button>
      <Input
          clearable
          v-model.trim="queryParams.name"
          placeholder="漏洞名称"
          @on-change="debounceFn"
          style="width: 180px;margin-left: 15px;" />
      <Input
          clearable
          v-model.trim="queryParams.cve"
          placeholder="CVE"
          @on-change="debounceFn"
          style="width: 180px;margin-left: 15px;" />
      <Input
          clearable
          v-model.trim="queryParams.cnnvd"
          placeholder="CNNVD"
          @on-change="debounceFn"
          style="width: 180px;margin-left: 15px;" />
      <Select filterable transfer 
          v-model="queryParams.level" 
          placeholder="漏洞评级"
          filterable
          clearable
          style="width:150px;text-align: left;margin-left: 15px;" 
          @on-change="changePageNow(1)">
          <Option 
            v-for="(val, key) in $ConfigurationParameter.VULNERABILITY_LEVEL_OPTIONS"
            :key="key"
            :value="key"
            :title="val">{{ val }}</Option>
      </Select>
      <Button
        type="primary"
        ghost
        style="height: 32px;margin-left: 9px;"
        @click="refreshQueryParams()">
        <i class="el-icon-refresh-right" />
      </Button>
    </template>
    <Modal
        v-model="modalData.show"
        :title="`${isAdd ? '创建' : '修改'}漏洞信息`"
        @on-visible-change="changeVisible"
        class="my-modal">
        <Form 
            ref="formInline"
            :label-width="110"
            :model="formInline" 
            :rules="ruleInline">
            <FormItem prop="name" label="漏洞名称">
                <Input clearable v-model="formInline.name"></Input>
            </FormItem>
            <FormItem prop="sulotion"  label="解决方法">
                <Input v-model="formInline.sulotion" type="textarea" :rows="3"></Input>
            </FormItem>
            <FormItem prop="publicUrl"  label="参考资料地址">
                <Input v-model="formInline.publicUrl"></Input>
            </FormItem>
            <div class="inline">
                <FormItem prop="cvssv2"  label="CVSSV2">
                    <Input v-model="formInline.cvssv2"></Input>
                </FormItem>
                <FormItem prop="cve"  label="CVE">
                    <Input v-model="formInline.cve"></Input>
                </FormItem>
            </div>
            <div class="inline">
                <FormItem prop="cwe"  label="CWE">
                    <Input v-model="formInline.cwe"></Input>
                </FormItem>
                <FormItem prop="tvid"  label="TVID">
                    <Input v-model="formInline.tvid"></Input>
                </FormItem>
            </div>
            <div class="inline">
                <FormItem prop="cnnvd"  label="CNNVD">
                    <Input v-model="formInline.cnnvd"></Input>
                </FormItem>
                <FormItem prop="isPlugin"  label="是否危险插件">
                    <RadioGroup clearable v-model="formInline.isPlugin">
                        <Radio label="Y">是</Radio>
                        <Radio label="N">否</Radio>
                    </RadioGroup>
                </FormItem>
            </div>
            <FormItem prop="value" label="威胁评分">
                <Input v-model="formInline.value" type="number"></Input>
            </FormItem>
            <FormItem prop="level" label="漏洞评级">
                <Select filterable transfer filterable clearable v-model="formInline.level" placeholder="">
                    <Option 
                        v-for="(val, key) in $ConfigurationParameter.VULNERABILITY_LEVEL_OPTIONS"
                        :key="key"
                        :value="key"
                        :title="val">{{ val }}</Option>
                </Select>
            </FormItem>
            <FormItem prop="description"  label="描述">
                <Input v-model="formInline.description" type="textarea" :rows="3"></Input>
            </FormItem>
        </Form>
        <div slot="footer" class="footer">
            <Button @click="modalData.show = false">取消</Button>
            <Button @click="saveVulnerability" :loading="modalData.loading" type="primary">确定</Button>
        </div>
    </Modal>
    <Drawer 
        v-model="drawerData.target" 
        title="靶标管理"
        class="my-drawer"
        :width="60">
        漏洞名称: {{ titleName }}
        <vulnerability-target 
            v-if="drawerData.target"
            ref="vulnerabilityTarget"
            :publicVulnerability="currentVulnerability"
            class="my-sub-element"></vulnerability-target>
    </Drawer>
    <Drawer 
        v-model="drawerData.environment" 
        title="验证环境"
        class="my-drawer"
        :width="60">
        漏洞名称: {{ titleName }}
        <vulnerability-environment 
            v-if="drawerData.environment"
            ref="vulnerabilityEnvironment"
            :publicVulnerability="currentVulnerability"
            class="my-sub-element"></vulnerability-environment>
    </Drawer>
    <Drawer title="POC管理" v-model="drawerData.poc" class="my-poc-manage" :width="60">
        <poc-manage 
            ref="pocManage" 
            :vulnerabilityId="currentPublicVulnerabilityId" 
            isPublic
            :vulnerabilityName="publicVulnerabilityName"></poc-manage>
    </Drawer>
  </MenuPage>
</template>
<script>
import PocManage from '@/view/testPlatform/components/poc-manage'
import VulnerabilityTarget from '@/view/testPlatform/components/vulnerability-target'
import VulnerabilityEnvironment from '@/view/testPlatform/components/vulnerability-environment'
import {templateUrl} from '@/view/testPlatform/asset/api/leak'
import { 
  queryCommonVulnerabilityList, 
  addCommonVulnerability,
  updateCommonVulnerability,
  deleteCommonVulnerability,
  getLeakUrl
} from '@/view/testPlatform/components/public-vulnerability-select-drawer/vulnerability'
import { debounce } from '@/libs/utils'

export default {
  name: 'VulnerabilityVerifyProject',
  components: {
    PocManage,
    VulnerabilityTarget,
    VulnerabilityEnvironment
  },
  data () {
    return {
        currentPublicVulnerabilityId: '',
        publicVulnerabilityName: '',
        currentVulnerability: {},
        titleName: '',
        drawerData: {
            target: false,
            environment: false,
            poc: false
        },
        resData: {
            total: 0,
            list: [],
            loading: true
        },
        queryParams: {
            pageIndex: 1,
            pageSize: 10,
            name: '',
            level: '',
            cve: '',
            cnnvd: ''
        },
        columns: [
            {
                title: '漏洞名称',
                key: 'name',
                tooltip: true,
            },
            {
                title: '漏洞评级',
                key: 'level',
                render: (h, params) => {
                    let ret = this.$CodeEscape.vulnerabilityLevelEscape(params.row.level)
                    return h('Tag', {
                        props: {
                            color: ret.color
                        },
                        style: {
                            width: '60px',
                            'text-align': 'center'
                        }
                    }, ret.text)
                }
            },
            {
                title: '数据来源',
                key: 'category',
                render: (h, params) => {
                    return h('Tag', {
                        props: {
                            color: params.row.category === 1 ? '#2db7f5' : '#19be6b'
                        },
                        style: {
                            width: '80px',
                            'text-align': 'center'
                        }
                    }, params.row.category === 1 ? '组件分析' : '用户添加')
                }
            },
            {
                title: '威胁评分',
                key: 'value',
                tooltip: true,
            },
            {
                title: 'CVSSV2',
                key: 'cvssv2',
                tooltip: true,
            },
            {
                title: 'CVE',
                key: 'cve',
                tooltip: true,
            },
            {
                title: 'CWE',
                key: 'cwe',
                tooltip: true,
            },
            {
                title: 'TVID',
                key: 'tvid',
                tooltip: true,
            },
            {
                title: 'CNNVD',
                key: 'cnnvd',
                tooltip: true,
            },
            {
              title: '操作',
              width: 290,
              slot: 'action',
              opList: [
                {

                  txt: '修改',
                  on:{
                    click:(data) => {
                      this.showAddModal(data)
                    }
                  },
                },
                {
                  txt: 'POC信息',
                  on:{
                    click:(data) => {
                      this.currentPublicVulnerabilityId = data.id
                      this.publicVulnerabilityName = data.name
                      this.$nextTick(() => {
                          this.drawerData.poc = true
                          this.$refs.pocManage.refreshQueryParams()
                      })
                    }
                  },
                },
                {
                  txt: '靶标管理',
                  on:{
                    click:(data) => {
                      this.currentVulnerability = data
                      this.titleName = data.name
                      this.drawerData.target = true
                    }
                  },
                },
                {
                  txt: '验证环境',
                  on:{
                    click:(data) => {
                      this.currentVulnerability = data
                      this.titleName = data.name
                      this.drawerData.environment = true
                    }
                  },
                },
                {
                  txt: '删除',
                  tooltip: true,
                  type: 'delete',
                  title: '确定要删除吗？',
                  on:{
                    click:(data) => {
                      this.deleteItem(data.id)
                    }
                  }
                }
              ]
            }
        ],
        modalData: {
          show: false,
          loading: false
        },
        formInline: {},
        ruleInline: {
            name: [
                { required: true, message: `名称不能为空`, trigger: 'blur,change' },
                { type:'string',max: 64,trigger:'blur,change',message:'最多输入64个字符' },
            ],
            level: [
                { required: true, message: `漏洞评级不能为空`, trigger: 'blur,change' }
            ],
        },
        isAdd: false
    }
  },
  mounted () {
    let getPage = this.$route.query.page ? parseInt(this.$route.query.page) : 1
    this.queryParams.pageIndex = getPage
    this.getCommonVulnerabilityList()
  },
  methods:{
      //漏洞导出
      exportLeak(){
        getLeakUrl({pageIndex:this.queryParams.pageIndex,pageSize:this.queryParams.pageSize}).then(res=>{
            if(res.data.code==1){
          let path = res.data.data;
          templateUrl({path}).then(res=>{
            const downloadElement = document.createElement('a');
            const href = window.URL.createObjectURL(res);
            downloadElement.href = href;
            downloadElement.download = `漏洞列表.xls`;
            document.body.appendChild(downloadElement);
            downloadElement.click();
            document.body.removeChild(downloadElement); // 下载完成移除元素
            window.URL.revokeObjectURL(href); // 释放掉blob对象
          })
        }else{
          this.$Message.error(res.data.message);
        }
      })
      },
      // 删除漏洞信息
      deleteItem(id) {
        deleteCommonVulnerability(id).then(({ data = {} }) => {
            let { code, message } = data
            if (code !== 1) {
                this.$Message.warning(message)
                return
            }
            this.$Message.success(`删除漏洞信息成功`)
            // 删除后展示当前页，当前页没有数据展示前一页
            this.queryParams.pageIndex = (this.resData.list.length == 1 && this.queryParams.pageIndex > 1) ?
                            this.queryParams.pageIndex - 1 : this.queryParams.pageIndex;
            this.getCommonVulnerabilityList()
        }).catch(() => {
            this.$Message.error(`删除漏洞信息异常`)
        })
      },
      // 隐藏模态框时，重置表单数据
      changeVisible(type) {
          if (!type) {
              this.$refs.formInline.resetFields()
              this.modalData.loading = false
          }
      },
      // 创建、修改公共漏洞信息
      saveVulnerability() {
        this.$refs.formInline.validate(valid => {
            if (valid) {
                this.modalData.loading = true
                let apiName = this.isAdd
                 ? addCommonVulnerability : updateCommonVulnerability
                 if (this.isAdd) { // 创建操作确认把id删掉，避免造成错误
                    delete this.formInline.id
                }
                apiName(this.formInline).then(({ data = {} }) => {
                    let { code, message } = data
                    if (code !== 1) {
                        this.$Message.warning(message)
                        return
                    }
                    // 创建成功
                    this.$Message.success(`${this.isAdd ? '创建' : '修改'}漏洞信息成功`)
                    this.modalData.show = false
                    this.refreshQueryParams()
                }).catch(() => {
                    this.$Message.error(`${this.isAdd ? '创建' : '修改'}漏洞信息异常`)
                }).finally(() => {
                    this.modalData.loading = false
                })
            }
        })
      },
      // 展示创建、修改公共漏洞信息的模态框
      showAddModal(data) {
        this.modalData.show = true
        this.isAdd = !data
        this.formInline = Object.assign({}, data || {
          name: '',
          sulotion: '',
          publicUrl: '',
          cvssv2: '',
          cve: '',
          cwe: '',
          tvid: '',
          cnnvd: '',
          isPlugin: 'Y',
          value: 1,
          level: '1',
          description: ''
        })
      },
      // 重置搜索条件并查询数据
      refreshQueryParams() {
          this.queryParams = {
            pageIndex: 1,
            pageSize: 10,
            name: '',
            level: '',
            cve: '',
            cnnvd: ''
          }
          this.getCommonVulnerabilityList()
      },
      // 防抖方法，用于输入型查询
      debounceFn: debounce(function() {
          this.changePageNow(1);
      }),
      // 查询指定页数据
      changePageNow(val) {
          this.queryParams.pageIndex = val;
          this.getCommonVulnerabilityList();
      },
      changePage(page){
        this.queryParams.pageIndex = page;
          this.getCommonVulnerabilityList();
      },
      changePageSize(size){
            this.queryParams.pageSize = size;
          this.getCommonVulnerabilityList();
      },
      // 查询公共漏洞信息列表
      getCommonVulnerabilityList() {
          this.resData.loading = true
          queryCommonVulnerabilityList(this.queryParams).then(({ data = {} }) => {
              let { code, message } = data
              data = data.data || {}
              if (code !== 1) {
                  this.$Message.warning(message)
                  return
              }
              this.resData = {
                  total: data.total || 0,
                  list: data.items || [],
                  loading: false
              }
          }).catch(() => {
              this.$Message.error('获取公共漏洞列表异常')
          }).finally(() => {
              this.resData.loading = false
          })
      },
  }
}
</script>
<style scoped>
.item-table {
  display: table;
  width: 100%;
  border: 1px solid #eee;
  table-layout: fixed;
  word-break: break-all;
}
.item-table p {
  display: table-row;
  line-height: 36px;
  text-align: center;
}
.item-table p span {
  display: table-cell;
  border-bottom: 1px solid #eee;
}
.ios-alert {
  /* position: absolute;
        top: -44px;
        right: -404px; */
  color: orange;
  font-size: 16px;
  cursor: pointer;
}
.too {
  position: absolute;
  left: 113px;
  top: -1px;
}
</style>
